Introduction to Object-Oriented Programming (OOP) in Dart
Object-Oriented Programming (OOP) is a programming approach in which software is organized around
objects and classes. Dart supports OOP and uses concepts such as classes, objects, constructors,
inheritance, polymorphism, abstraction, and encapsulation.
OOP is especially important for Flutter development because Flutter applications are built using Dart and make extensive
use of classes, objects, constructors, inheritance, and reusable components.
The JustAcademy Flutter curriculum includes Object-Oriented Programming in Dart, along with
classes, objects, constructors, inheritance, polymorphism, and abstraction under Dart Programming
Fundamentals. :contentReference[oaicite:0]{index=0}
Visit JustAcademy Flutter Training
1. What Is Object-Oriented Programming?
Object-Oriented Programming is a programming methodology that represents real-world entities as
objects. Each object can contain data and functions that operate on that data.
For example, consider a mobile application that manages students. A student can have properties such as:
- Name
- Age
- Email
- Course
- Marks
The student can also perform actions such as:
- Display information
- Calculate marks
- Update profile
- Check result
In OOP, these properties and behaviors can be represented using a Student class.
class Student {
String name;
int age;
void displayInfo() {
print("Name: $name");
print("Age: $age");
}
}
2. Why Do We Use OOP?
OOP helps developers create applications that are easier to organize, reuse, maintain, and extend.
Main Benefits of OOP
- Code Reusability: Existing classes and methods can be reused.
- Organization: Related data and behavior can be grouped together.
- Maintainability: Code can be easier to modify and maintain.
- Scalability: Applications can be extended using new classes and relationships.
- Security: Encapsulation can control access to internal data.
- Flexibility: Polymorphism allows different implementations through common interfaces.
- Abstraction: Unnecessary implementation details can be hidden.
3. OOP in Dart
Dart is an object-oriented programming language. Dart applications commonly use classes and objects to structure
application logic.
A simplified OOP structure can be understood as:
Class
↓
Object
↓
Properties + Methods
↓
Application Behavior
For example:
class Car {
String brand = "Toyota";
void drive() {
print("The car is driving");
}
}
void main() {
Car car = Car();
print(car.brand);
car.drive();
}
Output:
Toyota
The car is driving
4. What Is a Class?
A class is a blueprint or template used to create objects.
It defines the properties and behaviors that objects created from the class can have.
A class can contain:
- Variables
- Properties
- Methods
- Constructors
- Getters and setters
- Other classes or objects
Basic Class Syntax
class ClassName {
// properties
// methods
}
Example
class Student {
String name = "Rahul";
int age = 21;
void study() {
print("$name is studying");
}
}
5. What Is an Object?
An object is an instance of a class.
A class defines the structure, while an object represents an actual instance created from that structure.
class Student {
String name = "Rahul";
void study() {
print("$name is studying");
}
}
void main() {
Student student = Student();
print(student.name);
student.study();
}
Here:
Student is the class.
student is the object.
name is a property.
study() is a method.
6. Class vs Object
| Class |
Object |
| Blueprint or template |
Instance of a class |
| Defines properties and behavior |
Uses those properties and behaviors |
| Does not represent a specific instance |
Represents a specific instance |
Example: Student |
Example: Student() |
7. Properties in a Class
Properties are variables defined inside a class. They represent the data or characteristics of an object.
class Product {
String name = "Laptop";
double price = 55000;
int quantity = 2;
}
Creating and accessing the object:
void main() {
Product product = Product();
print(product.name);
print(product.price);
print(product.quantity);
}
8. Methods in a Class
A method is a function defined inside a class. Methods describe actions or behaviors that an object can perform.
class Calculator {
int add(int a, int b) {
return a + b;
}
int subtract(int a, int b) {
return a - b;
}
}
void main() {
Calculator calculator = Calculator();
print(calculator.add(10, 20));
print(calculator.subtract(20, 5));
}
Output:
30
15
9. Constructors
A constructor is a special method used when creating an object.
Constructors are commonly used to initialize an object's properties.
Basic Constructor
class Student {
String name;
int age;
Student(this.name, this.age);
}
void main() {
Student student = Student("Aman", 22);
print(student.name);
print(student.age);
}
Output:
Aman
22
10. Why Constructors Are Useful
Constructors allow objects to be created with different values instead of defining the same values inside the class.
class User {
String name;
String email;
User(this.name, this.email);
}
void main() {
User user1 = User(
"Rahul",
"[email protected]",
);
User user2 = User(
"Priya",
"[email protected]",
);
print(user1.name);
print(user2.name);
}
Both objects use the same class but contain different data.
11. The this Keyword
The this keyword refers to the current object.
It is frequently used when constructor parameters have the same names as class properties.
class Employee {
String name;
double salary;
Employee(this.name, this.salary);
}
Here, this.name refers to the property of the current object.
12. Encapsulation
Encapsulation means keeping data and the methods that operate on that data together and controlling how
the internal data is accessed or modified.
Dart uses an underscore prefix to make an identifier library-private.
class BankAccount {
double _balance = 0;
void deposit(double amount) {
if (amount > 0) {
_balance += amount;
}
}
double getBalance() {
return _balance;
}
}
void main() {
BankAccount account = BankAccount();
account.deposit(5000);
print(account.getBalance());
}
The internal _balance variable is not intended to be accessed directly from outside its library.
Public methods can provide controlled operations.
13. Getters
A getter provides a property-like way to read a value.
class Person {
String name;
Person(this.name);
String get displayName => name;
}
void main() {
Person person = Person("Rahul");
print(person.displayName);
}
Output:
Rahul
14. Setters
A setter provides a controlled way to assign a value to a property.
class User {
String _name = "";
String get name => _name;
set name(String value) {
if (value.isNotEmpty) {
_name = value;
}
}
}
void main() {
User user = User();
user.name = "Aman";
print(user.name);
}
15. Inheritance
Inheritance allows one class to inherit properties and methods from another class.
The existing class is commonly called the parent or superclass, while the new class is called the child or subclass.
class Animal {
void eat() {
print("Animal is eating");
}
}
class Dog extends Animal {
void bark() {
print("Dog is barking");
}
}
void main() {
Dog dog = Dog();
dog.eat();
dog.bark();
}
Output:
Animal is eating
Dog is barking
The Dog class receives the eat() method from Animal.
16. Why Inheritance Is Useful
- Encourages code reuse.
- Allows specialized classes to extend general classes.
- Reduces duplication.
- Creates relationships between related types.
- Supports polymorphism.
17. Method Overriding
A subclass can provide its own implementation of a method inherited from a superclass.
This is called method overriding.
class Animal {
void sound() {
print("Animal makes a sound");
}
}
class Dog extends Animal {
@override
void sound() {
print("Dog barks");
}
}
void main() {
Dog dog = Dog();
dog.sound();
}
Output:
Dog barks
18. Polymorphism
Polymorphism means that the same interface or method call can work with different types and produce
type-specific behavior.
class Animal {
void sound() {
print("Animal sound");
}
}
class Dog extends Animal {
@override
void sound() {
print("Dog barks");
}
}
class Cat extends Animal {
@override
void sound() {
print("Cat meows");
}
}
void main() {
Animal animal1 = Dog();
Animal animal2 = Cat();
animal1.sound();
animal2.sound();
}
Output:
Dog barks
Cat meows
Both variables use the Animal type, but the actual objects determine which implementation runs.
19. Abstraction
Abstraction means exposing the important functionality while hiding implementation details.
Dart supports abstract classes that can define behavior that subclasses must implement.
abstract class Shape {
double calculateArea();
}
class Circle extends Shape {
double radius;
Circle(this.radius);
@override
double calculateArea() {
return 3.14 * radius * radius;
}
}
void main() {
Circle circle = Circle(5);
print(circle.calculateArea());
}
The Shape class defines what a shape should provide, while Circle supplies the implementation.
20. Interface Concept in Dart
In Dart, every class implicitly defines an interface. A class can implement another class using the
implements keyword.
class Animal {
void sound() {
print("Animal sound");
}
}
class Dog implements Animal {
@override
void sound() {
print("Dog barks");
}
}
When using implements, the implementing class must provide the required members of the interface.
21. Composition
Composition means building a class using objects of other classes.
Instead of inheriting behavior, one class can contain another object.
class Engine {
void start() {
print("Engine started");
}
}
class Car {
Engine engine = Engine();
void startCar() {
engine.start();
print("Car started");
}
}
void main() {
Car car = Car();
car.startCar();
}
Here, the Car contains an Engine object.
22. Static Members
A static member belongs to the class itself rather than a particular object.
class Calculator {
static int add(int a, int b) {
return a + b;
}
}
void main() {
print(Calculator.add(10, 20));
}
Because add() is static, it can be accessed using the class name without creating a Calculator object.
23. Named Constructors
Dart also supports named constructors, which can provide different ways to create objects.
class User {
String name;
User(this.name);
User.guest() : name = "Guest";
}
void main() {
User user1 = User("Rahul");
User user2 = User.guest();
print(user1.name);
print(user2.name);
}
Output:
Rahul
Guest
24. Factory Constructors
A factory constructor can control how an instance is created and can return an existing instance or a different
implementation.
class User {
String name;
User._internal(this.name);
factory User(String name) {
return User._internal(name);
}
}
void main() {
User user = User("Aman");
print(user.name);
}
Factory constructors are useful in situations where object creation needs additional logic.
25. OOP Relationships
| Concept |
Meaning |
Dart Feature |
| Class |
Blueprint for objects |
class |
| Object |
Instance of a class |
ClassName() |
| Encapsulation |
Controls access to data and behavior |
_privateMember, getters, setters |
| Inheritance |
Reuses and extends another class |
extends |
| Polymorphism |
Different implementations through a common type |
Overriding |
| Abstraction |
Hides implementation details |
abstract |
| Interface |
Defines a contract that a class can implement |
implements |
| Composition |
Builds classes using other objects |
Object properties |
26. Real-World E-Commerce Example
OOP can be used to model products in an e-commerce application.
class Product {
String name;
double price;
Product(this.name, this.price);
void displayProduct() {
print("Product: $name");
print("Price: ₹$price");
}
}
void main() {
Product product = Product(
"Laptop",
55000,
);
product.displayProduct();
}
Here, the Product class represents the structure of a product, while each Product object can represent
a specific product.
27. Real-World Student Management Example
class Student {
String name;
int marks;
Student(this.name, this.marks);
String getResult() {
if (marks >= 40) {
return "Pass";
}
return "Fail";
}
void display() {
print("Name: $name");
print("Marks: $marks");
print("Result: ${getResult()}");
}
}
void main() {
Student student = Student("Aman", 75);
student.display();
}
Output:
Name: Aman
Marks: 75
Result: Pass
28. OOP and Flutter
OOP concepts are closely connected with Flutter development because Flutter applications are written in Dart and use classes
extensively.
Examples of OOP usage in Flutter include:
- Widgets are represented using classes.
- Stateful and stateless components are implemented through classes.
- Constructors are commonly used to configure widgets.
- Models can be represented using Dart classes.
- Services can be organized into classes.
- Repositories can be represented as classes.
- State-management structures can use classes and objects.
- API response models can be represented using Dart classes.
Simple Flutter Widget Example
class WelcomeScreen extends StatelessWidget {
const WelcomeScreen({super.key});
@override
Widget build(BuildContext context) {
return const Scaffold(
body: Center(
child: Text("Welcome to Flutter"),
),
);
}
}
This example demonstrates how a Flutter UI component is represented as a Dart class.
29. Model Class Example for Flutter
Model classes are commonly used to represent application data.
class User {
final int id;
final String name;
final String email;
User({
required this.id,
required this.name,
required this.email,
});
}
void main() {
User user = User(
id: 1,
name: "Rahul",
email: "[email protected]",
);
print(user.name);
print(user.email);
}
30. Four Major Pillars of OOP
1. Encapsulation
Bundles data and behavior together while controlling access to internal data.
2. Inheritance
Allows a class to reuse or extend functionality from another class.
3. Polymorphism
Allows different objects to provide different implementations through a common interface or parent type.
4. Abstraction
Hides unnecessary implementation details and exposes the important functionality.
| Pillar |
Main Purpose |
Common Dart Feature |
| Encapsulation |
Protect and organize data |
Private members, getters, setters |
| Inheritance |
Reuse and extend functionality |
extends |
| Polymorphism |
Support multiple implementations |
@override |
| Abstraction |
Hide implementation details |
abstract |
31. Advantages of OOP in Flutter Projects
- Helps organize large Flutter applications.
- Encourages reusable application components.
- Makes application models easier to structure.
- Supports separation of responsibilities.
- Can make business logic easier to maintain.
- Works naturally with Flutter's class-based widget system.
- Supports scalable application architecture.
- Makes it easier to represent real-world entities such as users, products, orders, and payments.
32. Common Beginner Mistakes in OOP
Mistake 1: Confusing a Class with an Object
class Car {
String brand = "Toyota";
}
The class is a blueprint. An object is created from it:
Car car = Car();
Mistake 2: Forgetting Constructor Initialization
When a class requires values during creation, make sure the constructor properly initializes them.
class User {
String name;
User(this.name);
}
Mistake 3: Overusing Inheritance
Not every relationship should be modeled through inheritance. Sometimes composition is a better way to structure related
functionality.
Mistake 4: Putting Too Much Logic into One Class
A class should have a clear responsibility. Large classes containing unrelated responsibilities can become difficult to maintain.
33. Best Practices for OOP in Dart
- Give classes meaningful names.
- Keep each class focused on a clear responsibility.
- Use constructors to initialize required data.
- Use private members when internal data should not be directly exposed.
- Use getters and setters when controlled access is useful.
- Use inheritance when there is a genuine parent-child relationship.
- Prefer composition when objects naturally contain other objects.
- Use abstract classes when a common contract or abstraction is needed.
- Use polymorphism to allow different implementations through a common type.
- Keep Flutter model, UI, and business logic responsibilities appropriately separated.
34. Complete OOP Example
abstract class Employee {
String name;
double salary;
Employee(this.name, this.salary);
void displayInfo() {
print("Name: $name");
print("Salary: ₹$salary");
}
double calculateBonus();
}
class Developer extends Employee {
Developer(
String name,
double salary,
) : super(name, salary);
@override
double calculateBonus() {
return salary * 0.10;
}
}
class Manager extends Employee {
Manager(
String name,
double salary,
) : super(name, salary);
@override
double calculateBonus() {
return salary * 0.20;
}
}
void main() {
Employee developer = Developer(
"Rahul",
60000,
);
Employee manager = Manager(
"Priya",
90000,
);
developer.displayInfo();
print("Bonus: ₹${developer.calculateBonus()}");
print("");
manager.displayInfo();
print("Bonus: ₹${manager.calculateBonus()}");
}
This example demonstrates several OOP concepts together:
- Abstract class
- Inheritance
- Constructors
- Method overriding
- Polymorphism
- Encapsulation through class structure
35. Practice Exercises
- Create a
Student class with name, age, and marks properties.
- Create a constructor for the
Student class.
- Add a method that displays student information.
- Create a
BankAccount class with deposit and withdrawal methods.
- Create a
Product class with name and price.
- Create multiple product objects with different values.
- Create an
Animal parent class and Dog and Cat subclasses.
- Override a method in the child classes.
- Create an abstract
Shape class and implement Circle and Rectangle.
- Create a Flutter model class for a user.
- Create a Flutter model class for an e-commerce product.
- Build a small Flutter screen using a custom class.
36. Quick Revision
| Concept |
Meaning |
| OOP |
Programming approach based on objects and classes |
| Class |
Blueprint for creating objects |
| Object |
Instance of a class |
| Property |
Data stored inside a class/object |
| Method |
Function defined inside a class |
| Constructor |
Initializes an object when it is created |
| Encapsulation |
Controls and organizes access to data |
| Inheritance |
Allows one class to extend another |
| Polymorphism |
Allows different implementations through a common type |
| Abstraction |
Hides implementation details |
| Interface |
Defines a contract that a class can implement |
| Composition |
Builds a class using objects of other classes |
37. Key Takeaways
- Dart is an object-oriented programming language.
- Classes act as blueprints for objects.
- Objects are instances of classes.
- Properties represent object data.
- Methods represent object behavior.
- Constructors initialize objects.
- Encapsulation controls access to internal data.
- Inheritance allows classes to reuse and extend functionality.
- Polymorphism allows different implementations through a common type.
- Abstraction hides unnecessary implementation details.
- OOP concepts are fundamental to understanding Flutter and Dart development.
38. Learn Flutter with JustAcademy
JustAcademy's Flutter course includes Dart Programming Fundamentals, including
Object-Oriented Programming in Dart, classes, objects, constructors, inheritance, polymorphism, and abstraction.
The broader curriculum also covers Flutter widgets, navigation, state management, API integration, Firebase, projects,
testing, deployment, and advanced Flutter development. :contentReference[oaicite:1]{index=1}
Explore JustAcademy Flutter Training
To register for a course demonstration:
Register for JustAcademy Course Demo